package br.eng.eliseu.gwt.aconchego.camera.server.service;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.List;

import javax.persistence.EntityManager;
import javax.persistence.Query;

import br.eng.eliseu.gwt.aconchego.camera.client.service.UsuarioService;
import br.eng.eliseu.gwt.aconchego.camera.module.AcessoCam;
import br.eng.eliseu.gwt.aconchego.camera.module.Camera;
import br.eng.eliseu.gwt.aconchego.camera.module.StatusCamEnum;
import br.eng.eliseu.gwt.aconchego.camera.module.Usuario;
import br.eng.eliseu.gwt.aconchego.camera.server.EMF;
import br.eng.eliseu.gwt.aconchego.camera.server.command.SendEmailCommand;

import com.google.gwt.user.server.rpc.RemoteServiceServlet;

public class UsuarioServiceImpl extends RemoteServiceServlet implements UsuarioService {

	private static final long serialVersionUID = 4311932377022043810L;

	@SuppressWarnings("unchecked")
	public Usuario gravaUsuario(Usuario usuario) throws Exception{
		EntityManager manager = EMF.currentEntityManager();
		try {
			manager.getTransaction().begin();
			
			// --- Verifica se o usuario ja existe
			List<Usuario> lista = new ArrayList<Usuario>();
			Query q;
			q = manager.createNamedQuery("usuario.selectPorEmail");
			q.setParameter("email", usuario.getEmail());
			
			lista = (List<Usuario>) q.getResultList();
			for (Usuario u : lista) {
				if (u.getId() != usuario.getId()){
					//--- Se encontrou um usuario com o mesmo email e o id for DIFERENTE 
					//    do id deste usuario � porque o email ja esta sendo usado por outro 
					throw new Exception("Ja existe um usuario cadastrado com este email ( "+u.getNome()+" )");
				}
			}
			
			usuario = manager.merge(usuario);
			manager.getTransaction().commit();

		} catch (Exception e) {
			System.out.println( e.getMessage() );
			throw new Exception(e.getMessage());
		} finally {
			EMF.closeEntityManager();
		}
		
		return usuario;
	}

	public AcessoCam gravaAcesso(AcessoCam acesso, Boolean enviaEmail) throws Exception {
		Boolean novo = (acesso.getId()==null)?true:false;

		// --- Grava o Usuario
		try {
			acesso.setUsuario(gravaUsuario(acesso.getUsuario()));
		} catch (Exception e1) {
			System.out.println( e1.getMessage() );
			throw new Exception(e1.getMessage());
		}
		
		// --- Se conseguiu gravar o usuario, gravo o acesso
		EntityManager manager = EMF.currentEntityManager();
		try {
			manager.getTransaction().begin();
			acesso = manager.merge(acesso);
			manager.getTransaction().commit();
			
		} catch (Exception e) {
			System.out.println( e.getMessage() );
		} finally {
			EMF.closeEntityManager();
		}
		
		acesso.repopulaListCameras();
		
		if (enviaEmail.booleanValue()){
			enviaEmailDeAviso(acesso, novo);
		}
		
		return acesso;
	}

	private void enviaEmailDeAviso(AcessoCam acesso, Boolean novo) {
		StringBuffer texto = new StringBuffer();
		texto.append("<h3>Olá "+acesso.getUsuario().getNome()+"</h3><br>");
		if (novo.booleanValue()){
			texto.append("Seu cadastramento no sistema de câmeras da Aconchego Hotel escola foi feito.<br><br>");
		}else{
			texto.append("Seu cadastramento no sistema de câmeras da Aconchego Hotel escola foi alterado.<br><br>");
		}
		texto.append("Seu usuario e senha de acesso foi definido da seguinte maneira.<br><br>");
		texto.append("Usuário: <b>"+acesso.getUsuario().getEmail()+"</b><br>");
		texto.append("Senha: <b>"+acesso.getUsuario().getSenha() +"</b><br><br>");
		texto.append("[Ao acessar o sistema você vai ter oportunidade de alterar esta senha, caso deseje]<br><br>");
		texto.append("Para acessar clique no link abaixo:<br>");
		texto.append("<a href='http://www.aconchegohotelescola.com.br/ao-vivo/'>câmeras ao vivo</a><br><br>");
//			DateTimeFormat fmtHora = DateTimeFormat.getFormat("HH:mm");
		SimpleDateFormat fmtHora = new SimpleDateFormat("HH:mm");
		texto.append("Seu cadastro consta das Seguintes informações<br><br>");
		texto.append("Status: "+acesso.getStatus().name()+"<br>");
		texto.append("Nome: "+acesso.getUsuario().getNome()+"<br>");
		texto.append("e-Mail: "+acesso.getUsuario().getEmail()+"<br>");
		texto.append("Grupo: "+acesso.getGrupo().name()+"<br>");
		if (acesso.getPeriodoInicio()==null){
			texto.append("Acesso no periodo: Durante todo o dia<br>");
		}else{
			texto.append("Acesso no periodo: "+fmtHora.format(acesso.getPeriodoInicio())+"h as ");
			texto.append(fmtHora.format(acesso.getPeriodoFim())+"h<br>");
		}
		texto.append("câmeras:<br>");
		for (Camera c : acesso.getCameras()) {
			texto.append(c.getNome()+"<br>");
		}
		texto.append("<br><br>");
		texto.append("No caso de alguma dúvida, entre em contato com a administração da escola<br><br>");
		texto.append("<b>Aconchego Hotel Escola<b><br>");
		texto.append("Fone: 034 3217 0747<br>");
		
		SendEmailCommand cmdEmail = new SendEmailCommand();
		cmdEmail.setSubject("Aconchego - Cadastro");
		cmdEmail.setRecipient(acesso.getUsuario().getEmail());
		cmdEmail.setText(new String(texto));
		cmdEmail.call();
	}

	@SuppressWarnings("unchecked")
	public List<Camera> getCameras() throws Exception {
		List<Camera> lista = new ArrayList<Camera>();

		EntityManager manager = EMF.currentEntityManager();
		try {
			Query q;
			manager.getTransaction().begin();
			q = manager.createNamedQuery("camera.selectStatus");
			q.setParameter("status", StatusCamEnum.ATIVADA);
			
			lista = (List<Camera>) q.getResultList();
			
			manager.getTransaction().commit();

		} catch (Exception e) {
			System.out.println( e.getMessage() );
		} finally {
			EMF.closeEntityManager();
		}

		return lista;
	}

	public Camera gravaCamera(Camera camera) {
		EntityManager manager = EMF.currentEntityManager();
		try {
			manager.getTransaction().begin();
			camera = manager.merge(camera);
			manager.getTransaction().commit();

		} catch (Exception e) {
			System.out.println( e.getMessage() );
		} finally {
			EMF.closeEntityManager();
		}
		return camera;
	}

	@SuppressWarnings("unchecked")
	public List<AcessoCam> listaUsuarios() throws Exception {
		List<AcessoCam> lista = new ArrayList<AcessoCam>();
		EntityManager manager = EMF.currentEntityManager();
		
        try {
			Query q;
			manager.getTransaction().begin();
			q = manager.createNamedQuery("acessoCam.selectTudo");

			lista = (List<AcessoCam>)q.getResultList();  

			manager.getTransaction().commit();

		} catch (Exception e) {
			System.out.println( e.getMessage() );
		} finally {
			EMF.closeEntityManager();
		}

		for (AcessoCam a : lista) {
			a.repopulaListCameras();
		}

		return lista;
	}

	
	@SuppressWarnings("unchecked")
	public boolean enviaSenha(String email) throws Exception {
		
		List<Usuario> lista = new ArrayList<Usuario>();
		EntityManager manager = EMF.currentEntityManager();
		try {
			Query q;
			manager.getTransaction().begin();
			q = manager.createNamedQuery("usuario.selectPorEmail");
			q.setParameter("email", email);
			q.setMaxResults(1);
			
			lista = (List<Usuario>) q.getResultList();
			
			manager.getTransaction().commit();

		} catch (Exception e) {
			System.out.println( e.getMessage() );
			throw new Exception( "Email n�o cadastrado, confira seu email ou contate a administra��o da Aconchego", null);
		} finally {
			EMF.closeEntityManager();
		}

		
		if(lista.size()>0){
			Usuario user = lista.get(0);
//			user.setSenha(StringUtil.randomString(4));
//			user = gravaUsuario(user);

			StringBuffer texto = new StringBuffer();
			texto.append("<h3>Olá "+user.getNome()+"</h3><br>");
			texto.append("Você está recebendo esse e-mail porque houve uma solicitação de recuperação de senha na Aconchego Hotel Escola.<br><br>");
			texto.append("Se foi você que solicitou esta recuperação, o seu usuário e senha, é: <br><br>");
			texto.append("Usuário: <b>"+user.getEmail()+"</b><br>");
			texto.append("Senha: <b>"+user.getSenha() +"</b><br><br>");
			texto.append("[Você pode tambem alterar sua senha dentro do ambiente do sistema]");

			texto.append("<br><br>");
			texto.append("No caso de alguma dúvida, entre em contato com a administração da escola<br><br>");
			texto.append("<b>Aconchego Hotel Escola<b><br>");
			texto.append("Fone: 034 3217 0747<br>");

			SendEmailCommand cmdEmail = new SendEmailCommand();
			cmdEmail.setSubject("Aconchego - Alteração de Senha");
			cmdEmail.setRecipient(email);
			cmdEmail.setText(new String(texto));
			cmdEmail.call();
			return true;
		} 
		throw new Exception("Usuario nao encontrado.", null);
	}

	public boolean trocaSenha(Usuario usuario) throws Exception {
		usuario = gravaUsuario(usuario);
		return false;
	}

	public List<AcessoCam> deletaUsuario(AcessoCam usuarioDeleta) throws Exception {
		EntityManager manager = EMF.currentEntityManager();
		try {
			manager.getTransaction().begin();
			manager.remove(manager.merge(usuarioDeleta));
			manager.getTransaction().commit();

		} catch (Exception e) {
			System.out.println( e.getMessage() );
		} finally {
			EMF.closeEntityManager();
		}
		return listaUsuarios();
	}

}
